/**
 * request 网络请求工具
 * 更详细的 api 文档: https://github.com/umijs/umi-request
 */
import type {
  RequestOptionsWithResponse,
  RequestResponse,
  RequestOptionsWithoutResponse,
  RequestOptionsInit,
  RequestMethod} from 'umi-request';
import {
  extend
} from 'umi-request';
import { Toast } from 'antd-mobile';

import { history } from 'umi';
import { storage,LOCALSTATE  } from '@/utils';
import Cookies from 'js-cookie'
// import { stringify } from 'querystring';
// import { getToken } from './authority';
// import { Redirect } from 'umi';

type ExtraOptions = { skipErrorHandler?: boolean; loading?: boolean };
export type MyRequestOptionsWithResponse = RequestOptionsWithResponse & ExtraOptions;
export type MyRequestOptionsWithoutResponse = RequestOptionsWithoutResponse & ExtraOptions;
export type MyRequestOptionsInit = RequestOptionsInit & ExtraOptions;

export interface RequestMethodInUmi<R = false> {
  <T = any>(url: string, options: MyRequestOptionsWithResponse): Promise<RequestResponse<T>>;
  <T = any>(url: string, options: MyRequestOptionsWithoutResponse): Promise<T>;
  <T = any>(url: string, options?: MyRequestOptionsInit): R extends true
    ? Promise<RequestResponse<T>>
    : Promise<T>;
}

const taskList = [];

const codeMessage = {
  200: '服务器成功返回请求的数据。',
  201: '新建或修改数据成功。',
  202: '一个请求已经进入后台排队（异步任务）。',
  204: '删除数据成功。',
  400: '发出的请求有错误，服务器没有进行新建或修改数据的操作。',
  401: '用户没有权限（令牌、用户名、密码错误）。',
  403: '用户得到授权，但是访问是被禁止的。',
  404: '发出的请求针对的是不存在的记录，服务器没有进行操作。',
  406: '请求的格式不可得。',
  410: '请求的资源被永久删除，且不会再得到的。',
  422: '当创建一个对象时，发生一个验证错误。',
  500: '服务器发生错误，请检查服务器。',
  502: '网关错误。',
  503: '服务不可用，服务器暂时过载或维护。',
  504: '网关超时。',
};

/**
 * 异常处理程序
 */
const errorHandler = (error) => {
  const { response, request } = error;
  const { skipErrorHandler } = request?.options ||{};
  
  if (response && response.status) {
    const errorText = codeMessage[response.status] || response.statusText;
    const { status, url } = response;
    if (!skipErrorHandler) {
      Toast.fail(`${errorText} ${status}: ${url}`);
    }
  } else if (!response) {
    Toast.offline('网络异常');
  }
  return response || { code: -999999 };
};

/**
 * 异常code处理
 * @param code
 */
const errorCodeHandler = (code) => {
  if (code === 401||code === 1004) {
    storage.remove('SESSION');
    history.replace('/login');
    // window.location.href = '/login';
  }
};

let requestMethodInstance: RequestMethod;
/**
 * 配置request请求时的默认参数
 */
const getRequestMethod = () => {
  // request method 已经实例化
  if (requestMethodInstance) {
    return requestMethodInstance;
  }

  requestMethodInstance = extend({
    method: 'post',
    errorHandler, // 默认错误处理
    prefix:'/api',
    credentials: 'include', // 默认请求是否带上cookie
  });

  /**
   * 请求前加个loading
   */
  requestMethodInstance.interceptors.request.use((url, options: any) => {
    taskList.push(1);
    if (!options.loading) {
      Toast.loading('', 0);
    }
    const local = storage.get(LOCALSTATE,true)
    const SESSION = storage.get('SESSION',true)
    if(SESSION){
      Cookies.set('SESSION',SESSION)
    }
    
    return {
      url,
      options: {
        ...options,
        headers: (local?.token)?{
          Authorization: `Bearer ${local.token}`, // token
        }:{},
      },
    };
  });

  requestMethodInstance.interceptors.response.use(
    async (response:any, options: MyRequestOptionsWithResponse) => {
      const data = await response.clone().json();
      taskList.pop();
      if (taskList.length <= 0) {
        Toast.hide();
      }
      
      if (data.code !== 1 && options.skipErrorHandler !== true) {
        Toast.fail(data.message || data.error || data.msg || '请求失败', 1.5, () =>
          errorCodeHandler(data.code),
        );
      }
      // response.data=response.data?response.data:response.response
      return response;
    },
  );
  return requestMethodInstance;
};

const request: RequestMethodInUmi = (url: any, options: any) => {
  const requestMethod = getRequestMethod();
  return requestMethod(url, options);
};

export default request;
